/**
 * 该模块提供用于表示指针或句柄的平台特定类型。
 * License: BSD
 * Authors: Lucifer (786325481@QQ.com)
 * Copyright: Copyright (C) 2008 Lucifer. All rights reserved.
 */

module system.IntPtr;

version(unittest)
{
	import system.Exception;
}

/**
 * 用于表示指针或句柄的平台特定类型。
 * Comments:
 *		IntPtr 类型被设计成整数，其大小适用于特定平台。
 *		即是说，此类型的实例在 32 位硬件和操作系统中将是 32 位，在 64 位硬件和操作系统上将是 64 位。
 *		IntPtr 也可用于保持句柄。
 */
public struct IntPtr
{
	private void* theValue;

	/**
	 * 使用指定的目标平台指针或句柄初始化 IntPtr 的新实例。
	 * Comments:
	 *		32 位为 4；64 位为 8。
	 */
	public this(size_t value)
	{
		theValue = cast(void*)value;
	}	

	/**
	 * 使用指定的指向未指定类型的指针来初始化 IntPtr 的新实例。
	 */
	public this(void* value)
	{
		theValue = value;
	}

	/**
	 * 一个只读字段，代表已初始化为零的指针或句柄。
	 */
	public static const IntPtr zero;

	/**
	 * 重载 == 。
	 */
	public bool opEquals(IntPtr other)
	{
		return theValue == other.theValue;
	}

	/**
	 * 返回此实例的散列值。
	 */
	public hash_t toHash()
	{
		return cast(hash_t)theValue;
	}

	/**
	 * 将此实例的值转换为整型。
	 * Comments:
	 *		32 位为 4；64 位为 8。
	 */
	public size_t toInteger()
	{
		return cast(size_t)theValue;
	}

	/**
	 * 返回此实例的大小。
	 * Comments:
	 *		32 位为 4；64 位为 8。
	 */
	public static size_t size()
	{
		return size_t.sizeof;
	}

	/**
	 * 将此示例转换为指针。
	 */
	public void* toPointer()
	{
		return theValue;
	}

	/**
	 * 重载强制转型。
	 */
	public size_t opCast()
	{
		return toInteger();
	}

	/// ditto
	public void* opCast()
	{
		return toPointer();
	}
}

unittest
{
	class TestIntPtr
	{
		void testSize()
		{
			
			version(X86)
			{
				if(IntPtr.size > 4)
					throw new OverflowException("It can not happen forever in 32 bit machine.");
			}
			else version(X86_64)
			{
				if(IntPtr.size > 8)
					throw new OverflowException("It can not happen forever in 64 bit machine.");
			}
		}
	}

	auto test = new TestIntPtr();
	test.testSize();
}